package com.yj.rselasticsearch.controller;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.metadata.IPage;
import com.baomidou.mybatisplus.extension.plugins.pagination.Page;
import com.yj.common.annotation.Log;
import com.yj.common.core.controller.BaseController;
import com.yj.common.core.domain.AjaxResult;
import com.yj.common.core.domain.entity.WarningInfo;
import com.yj.common.enums.BusinessType;
import com.yj.common.exception.ServiceException;
import com.yj.common.utils.FastUtils;
import com.yj.common.utils.StringUtils;
import com.yj.common.utils.poi.ExcelUtil;
import com.yj.rselasticsearch.domain.dto.WarningInfoDto;
import com.yj.rselasticsearch.service.ElasticsearchService;
import com.yj.rselasticsearch.service.WarningInfoService;
import io.swagger.annotations.Api;
import io.swagger.annotations.ApiImplicitParam;
import io.swagger.annotations.ApiImplicitParams;
import io.swagger.annotations.ApiOperation;
import lombok.extern.slf4j.Slf4j;
import org.springframework.security.access.prepost.PreAuthorize;
import org.springframework.transaction.annotation.Transactional;
import org.springframework.web.bind.annotation.*;
import org.springframework.web.multipart.MultipartFile;
import cn.afterturn.easypoi.excel.ExcelImportUtil;
import cn.afterturn.easypoi.excel.entity.ImportParams;

import javax.annotation.Resource;
import javax.servlet.http.HttpServletResponse;
import java.io.IOException;
import java.util.Calendar;
import java.util.LinkedList;
import java.util.List;

/**
 * (warningInfo)表控制层
 *
 * @author luoy
 */
@RestController
@Slf4j
@Api("告警信息")
@RequestMapping("/warning")
public class WarningInfoController extends BaseController {
    @Resource
    private WarningInfoService warningInfoService;
    @Resource
    private ElasticsearchService elasticsearchService;

    /**
     * 通过主键查询单条数据
     *
     * @param id 主键
     * @return 单条数据
     */
    @ApiOperation("查看单条告警信息明细")
    @ApiImplicitParam(name = "id", value = "数据id", dataType = "Integer", dataTypeClass = Integer.class)
    @GetMapping("selectOne")
    public AjaxResult selectOne(Integer id) {
        return AjaxResult.success(warningInfoService.selectByPrimaryKey(id));
    }

    /**
     * 导入excel
     *
     * @param file
     * @throws Exception
     */
    @PreAuthorize("@ss.hasPermi('warning:list:import')")
    @ApiOperation("导入告警信息excel")
    @Log(title = "知识库管理-告警信息维护", businessType = BusinessType.IMPORT)
    @ApiImplicitParam(name = "file", value = "excel", dataType = "MultipartFile", dataTypeClass = MultipartFile.class)
    @PostMapping("importExcel")
    public AjaxResult importExcel(@RequestParam("file") MultipartFile file) {
        ImportParams importParas = new ImportParams();
        importParas.setHeadRows(1);
        List<WarningInfo> list = null;
        try {
            list= ExcelImportUtil.importExcel(file.getInputStream(), WarningInfo.class, importParas);
        }catch (IOException ie){
            ie.printStackTrace();
            throw new ServiceException(String.format("Excel解析失败，请核对文件格式！%s",ie.getMessage()));
        }catch (Exception ex){
            ex.printStackTrace();
            throw new ServiceException(String.format("Excel解析失败，请联系管理员！%s",ex.getMessage()));
        }

        List<String> resultList = new LinkedList<>();
        List<WarningInfo> insertWarn = new LinkedList<>();
        for (int i = 0; i < list.size(); i++) {
            String result = null;
            if (StringUtils.isEmpty(list.get(i).getCategory())) {
                result = String.format("第%s行，'所属分类'不能为空", i+1);

            }
            if (StringUtils.isEmpty(list.get(i).getProducer())) {
                if (!FastUtils.checkNull(result)) {
                    result += String.format(",'产品厂家'不能为空");
                } else {
                    result = String.format("第%s行，'产品厂家'不能为空", i+1);
                }
            }

            if (StringUtils.isEmpty(list.get(i).getQuestion())) {
                if (!FastUtils.checkNull(result)) {
                    result += String.format(",'告警名称'不能为空");
                } else {
                    result = String.format("第%s行，'告警名称'不能为空", i+1);
                }
            }

            if (StringUtils.isEmpty(list.get(i).getAlarmInterpretation())) {
                if (!FastUtils.checkNull(result)) {
                    result += String.format(",'告警解释'不能为空");
                } else {
                    result = String.format("第%s行，'告警解释'不能为空", i+1);
                }
            }

            if (StringUtils.isEmpty(list.get(i).getWarningReason())) {
                if (!FastUtils.checkNull(result)) {
                    result += String.format(",'告警原因'不能为空");
                } else {
                    result = String.format("第%s行，'告警原因'不能为空", i+1);
                }
            }

            if (StringUtils.isEmpty(list.get(i).getMethodHanld())) {
                if (!FastUtils.checkNull(result)) {
                    result += String.format(",'现场处理措施'不能为空");
                } else {
                    result = String.format("第%s行，'现场处理措施'不能为空", i+1);
                }
            }
            result+="<br/>";
            if (FastUtils.checkNull(result)) {
                insertWarn.add(list.get(i));
            } else {
                resultList.add(result);
            }
        }


        insertWarn.forEach(data -> {
            data.setCreateTime(Calendar.getInstance().getTime());
            data.setUpdateTime(Calendar.getInstance().getTime());
        });
        if (!FastUtils.checkNullOrEmpty(insertWarn)) {
            boolean result = warningInfoService.saveBatch(insertWarn);
            if (result) {
                try {
                    boolean result1 = elasticsearchService.insert(insertWarn);
                    if (result1) {
                        return AjaxResult.success(String.format("导入成功%行，导入失败%行", insertWarn.size(), list.size() - insertWarn.size()));
                    }
                } catch (RuntimeException rx) {
                    log.info(rx.getMessage());

                    //es超时断线，如果失败就重试一次
                    try {
                        boolean result1 = elasticsearchService.insert(insertWarn);
                        if (result1) {
                            wait(5);
                            return AjaxResult.success(String.format("导入成功%行，导入失败%行", insertWarn.size(), list.size() - insertWarn.size()));
                        }
                    } catch (Exception exe) {
                        throw new ServiceException(exe.getMessage());
                    }
                }catch (Exception exe){
                    exe.printStackTrace();
                    throw  new ServiceException(String.format("模板导入操作异常，请联系管理员！%",exe.getMessage()));
                }
            }
        }
        String returnResult = String.format("<p>导入成功%s行，导入失败%s行;</p>" +
                "<br/>导入明细：<br/>%s", insertWarn.size(), list.size() - insertWarn.size(),resultList);
        return  AjaxResult.success(returnResult);
    }

    /**
     * 分页查询所有数据
     *
     * @param warningInfoDto
     * @return
     */
    @PreAuthorize("@ss.hasPermi('warning:list:query')")
    @ApiOperation("分页查询所有告警数据")
    @PostMapping("queryAllData")
    @ApiImplicitParams({
            @ApiImplicitParam(name = "pageIndex", value = "页码", dataType = "Integer", dataTypeClass = Integer.class),
            @ApiImplicitParam(name = "pageSize", value = "每页条数", dataType = "Integer", dataTypeClass = Integer.class),
            @ApiImplicitParam(name = "question", value = "问题", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "warningLeve", value = "告警级别", dataType = "String", dataTypeClass = String.class)

    })
    public AjaxResult queryAllData(@RequestBody WarningInfoDto warningInfoDto) {
      return warningInfoService.queryAllData(warningInfoDto);
    }

    /**
     * 新增数据
     *
     * @param warningInfo
     * @return
     */
    @PreAuthorize("@ss.hasPermi('warning:list:add')")
    @ApiOperation("新增数据")
    @Log(title = "知识库管理-告警信息维护", businessType = BusinessType.INSERT)
    @ApiImplicitParams({
            @ApiImplicitParam(name = "category", value = "所属分类", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "producer", value = "产品厂家", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "mouldName", value = "所属模块", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "partName", value = "所属单元", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "question", value = "告警名称", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "alarmInterpretation", value = "告警解释", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "warningLeve", value = "告警级别", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "warningReason", value = "告警原因", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "methodHanld", value = "现场处理措施", dataType = "String", dataTypeClass = String.class)
    })
    @PutMapping("addWarning")
    @Transactional(rollbackFor = Exception.class)
    public AjaxResult addWaring(@RequestBody WarningInfo warningInfo) {
        int result = warningInfoService.insertSelective(warningInfo);
        boolean result1 = false;
        if (result > 0) {
            List<WarningInfo> list = new LinkedList<>();
            list.add(warningInfo);
            try {
                result1 = elasticsearchService.insert(list);
            }catch (Exception ex){
                log.info(ex.getMessage());
                try {
                    //触发重试
                    wait(5);
                    result1 = elasticsearchService.insert(list);
                }catch (Exception e){
                    e.printStackTrace();
                    throw new ServiceException(String.format("新增数据失败，请联系管理员！%s",e.getMessage()));
                }
            }

        }
        if (result1) {
            return AjaxResult.success();
        }
        return AjaxResult.error();
    }

    /**
     * 更新告警信息
     *
     * @param warningInfo
     * @return
     */
    @PreAuthorize("@ss.hasPermi('warning:list:update')")
    @ApiOperation("更新告警信息")
    @Log(title = "知识库管理-告警信息维护", businessType = BusinessType.UPDATE)
    @ApiImplicitParams({
            @ApiImplicitParam(name = "id", value = "数据id", dataType = "Integer", dataTypeClass = Integer.class),
            @ApiImplicitParam(name = "mouldName", value = "所属模块", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "partName", value = "所属单元", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "question", value = "问题", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "warningLeve", value = "告警级别", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "reason", value = "存在原因", dataType = "String", dataTypeClass = String.class),
            @ApiImplicitParam(name = "methodHanld", value = "处理方法", dataType = "String", dataTypeClass = String.class)
    })
    @PutMapping("updateWarning")
    @Transactional(rollbackFor = Exception.class)
    public AjaxResult updateWarning(@RequestBody WarningInfo warningInfo) {
        Integer result = warningInfoService.updateByPrimaryKeySelective(warningInfo);
        if (result > 0) {
            try {
                boolean result1 = elasticsearchService.update(warningInfo);
            }catch (Exception ex){
                log.info(ex.getMessage());
                try {
                    wait(5);
                    boolean result1 = elasticsearchService.update(warningInfo);
                    if (result1) {
                        return AjaxResult.success();
                    }
                }catch (Exception e){
                    e.printStackTrace();
                    return AjaxResult.error(String.format("系统错误，请联系管理员！%s",e.getMessage()));
                }
            }


        }
        return AjaxResult.error();
    }


    /**
     * 告警信息模块生成
     * @param response
     */
    @ApiOperation("更新告警信息")
    @Log(title = "知识库管理-告警信息维护-导入模板下载", businessType = BusinessType.INSERT)
    @PostMapping("importTemplate")
    public void importTemplate(HttpServletResponse response){
        ExcelUtil<WarningInfo> util = new ExcelUtil<WarningInfo>(WarningInfo.class);
        util.importTemplateExcel(response, "告警信息");
    }

    /**
     * 删除告警信息
     *
     * @param warningInfo
     * @return
     */
    @PreAuthorize("@ss.hasPermi('warning:list:delete')")
    @ApiOperation("删除告警信息")
    @Log(title = "知识库管理-告警信息维护", businessType = BusinessType.DELETE)
    @DeleteMapping("deleteWarning")
    @ApiImplicitParam(name = "id", value = "数据id", dataType = "Integer", dataTypeClass = Integer.class)
    @Transactional(rollbackFor = ServiceException.class)
    public AjaxResult deleteWaring(@RequestBody WarningInfo warningInfo) {
        boolean result = warningInfoService.removeById(warningInfo);
        if (result) {
            try {
                result = elasticsearchService.delete(warningInfo);
                if (result) {
                    return AjaxResult.success();
                }
            }catch (Exception e){
                e.getMessage();
                try {
                    wait(5);
                    result = elasticsearchService.delete(warningInfo);
                }catch (Exception ex){
                    throw new ServiceException(String.format("系统错误，请联系管理员！%s",ex.getMessage()));
                }
            }
        }
        return AjaxResult.error();
    }
}
